package com.mars.service;

import com.google.common.collect.Interner;
import com.google.common.collect.Lists;
import com.mars.common.RequestHolder;
import com.mars.dao.SysAclMapper;
import com.mars.dao.SysRoleAclMapper;
import com.mars.dao.SysRoleUserMapper;
import com.mars.pojo.SysAcl;
import com.mars.pojo.SysUser;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

/**
 *
 * 核心权限service
 * @author MARS
 * @date 2018/2/5
 */
@Service
public class SysCoreService {

    @Resource
    private SysAclMapper sysAclMapper;

    @Resource
    private SysRoleUserMapper sysRoleUserMapper;

    @Resource
    private SysRoleAclMapper sysRoleAclMapper;

    /**
     * 获取当前用户的权限列表
     * @return
     */
    public List<SysAcl> getCurrentUserAclList() {
        // 获取当前用户id
        int userId = RequestHolder.getCurrentUser().getId();
        // 查询对应权限点
        return getUserAclList(userId);
    }

    /**
     * 获取当前角色的权限列表
     * @return
     */
    public List<SysAcl> getRoleAclList (int roleId) {
        List<Integer> aclIdList = sysRoleAclMapper.getAclIdListByRoleIdList(Lists.<Integer>newArrayList(roleId));
        if (CollectionUtils.isEmpty(aclIdList)) {
            return Lists.newArrayList();
        }
        return sysAclMapper.getByIdList(aclIdList);
    }


    public List<SysAcl> getUserAclList(int userId) {
        // 如果是超级管理员，获取所有权限
        if (isSuperAdmin()) {
            return sysAclMapper.getAll();
        }

        // 获取当前用户已经分配的角色id
        List<Integer> userRoleIdList = sysRoleUserMapper.getRoleIdListByUserId(userId);
        if (CollectionUtils.isEmpty(userRoleIdList)) {
            return Lists.newArrayList();
        }

        // 分配角色权限的并集,获取用户权限的总和
        List<Integer> userAclIdList = sysRoleAclMapper.getAclIdListByRoleIdList(userRoleIdList);
        if (CollectionUtils.isEmpty(userAclIdList)) {
            return Lists.newArrayList();
        }

        return sysAclMapper.getByIdList(userAclIdList);

    }

    /**
     * 判断是否是超级用户
     *
     */
    public boolean isSuperAdmin() {
        // 自定义一个识别管理员的方法
        // 这里是我自己定义了一个假的超级管理员规则，实际中要根据项目进行修改
        // 可以是配置文件获取，可以指定某个用户，也可以指定某个角色
        SysUser sysUser = RequestHolder.getCurrentUser();
        if (sysUser.getMail().contains("admin")) {
            return true;
        }
        return true;
    }

    // 判断是否可访问url
    public boolean hasUrlAcl(String url) {
        // 判断用户是否是超级管理员
        if (isSuperAdmin()) {
            return true;
        }

        List<SysAcl> aclList = sysAclMapper.getByUrl(url);
        if (CollectionUtils.isEmpty(aclList)) {
            return true; //有权限
        }

        List<SysAcl> userAclList = getCurrentUserAclList();
        Set<Integer> userAclIdSet = userAclList.stream().map(sysAcl -> sysAcl.getId()).collect(Collectors.toSet());
        // 用户是否拥有该权限点：规则，只要有一个权限点有权限，我们认为其有访问权限
        boolean hasValidAcl = false;
        for (SysAcl acl : aclList) {
            // 判断用户是否有访问权限
            if (acl == null || acl.getStatus() !=1 ) { // 权限点是无效的
                continue;
            }

            // 有效
            hasValidAcl = true;
            if (userAclIdSet.contains(acl.getId())){
                return true;
            }
        }
        if (!hasValidAcl){
            return true;
        }
        return false;
    }
}
